<template>
  <a-card :bordered="false">
    <a-space v-if="!fromSearchPath">
      <div style="width: 200px;height: 200px;border-radius: 5px;overflow: hidden;  ">
        <img style="width: 100%; height: 100%" :src="preUrl + playlist.imageUrl">
      </div>
      <a-space size="small" direction="vertical" style="margin-left: 12px">
        <div style="height:30px;display: inline-block;">
          <a-space align="center">
            <a-tag color="red">歌单</a-tag>
            <span style="font-size: 25px;font-weight: 600;color: #000000;height: 42px;display: inline-block;margin-left: -8px">{{ playlist.playlistName }}</span>
          </a-space>
        </div>
        <div style="height:25px;display: inline-block;">
          <a-space align="center">
            <img :src="preUrl + playlist.avatar" style="width: 25px;height:25px;border-radius: 100px" />
            <a style="color: #507daf" @click="goToSelfCenter">{{ playlist.userName }}</a>
            <span style="color: #676767">{{ playlist.gmtCreate.substr(0, 10) }}创建</span>
          </a-space>
        </div>
        <div style="height: 35px">
          <a-icon type="folder-add" class="icon"/>
          <a-button style="padding: 0 5px 0 40px;border-radius: 20px;height: 32px;width: fit-content" type="danger" v-if="playlist.isCollect === 0" @click="collectPlaylist">收藏<span style="color: gainsboro">（{{ playlist.collectors }}）</span></a-button>
          <a-popconfirm
            title="确定要取消收藏该歌单吗？"
            placement="rightTop"
            ok-text="是"
            cancel-text="否"
            @confirm="cancelCollectPlaylist()"
            v-else
          >
            <a-button style="padding: 0 5px 0 40px;border-radius: 20px;height: 32px;width: fit-content" type="danger">已收藏<span style="color: gainsboro">（{{ playlist.collectors }}）</span></a-button>
          </a-popconfirm>
        </div>
        <span>标签：{{ tagText }}</span>
        <span>歌曲：{{ totalCount }}&emsp;下载次数：{{ downloadCount }}</span>
        <span style="color: #676767">简介：{{ playlist.playlistInfo ? playlist.playlistInfo : '暂无' }}</span>
      </a-space>
    </a-space>
    <div class="table-page-search-wrapper" style="margin-top: 20px" v-if="!fromSearchPath">
      <a-form layout="inline">
        <a-row :gutter="48">
          <a-col :md="6" :sm="24">
            <a-form-item label="歌名">
              <a-input v-model="queryParam.songName" placeholder="查询歌名" @change="$refs.table.refresh(true)"/>
            </a-form-item>
          </a-col>
          <a-col :md="6" :sm="24">
            <a-form-item label="歌手">
              <a-input v-model="queryParam.singerName" placeholder="查询歌手" @change="$refs.table.refresh(true)"/>
            </a-form-item>
          </a-col>
          <a-col :md="6" :sm="24">
            <a-form-item label="专辑">
              <a-input v-model="queryParam.albumName" placeholder="查询专辑" @change="$refs.table.refresh(true)"/>
            </a-form-item>
          </a-col>
        </a-row>
      </a-form>
    </div>

    <s-table
      ref="table"
      size="default"
      rowKey="key"
      :columns="columns"
      :data="loadData"
      :alert="options.alert"
      :rowSelection="options.rowSelection"
      showPagination="auto"
    >
      <span slot="contributor" slot-scope="text, record">
        <a-button :title="text" class="ant-tag-red" style="height: 28px;font-size: 13px;padding: 0 5px" @click="goUserInfo(record)">{{ text | longTextFilter }}</a-button>
      </span>
      <span slot="action" slot-scope="text, record">
        <template>
          <a @click="goListen(record, $event)">在线试听</a>
          <a-divider type="vertical"/>
          <!--          <a-spin style="position: absolute; visibility: hidden; width: 28px">-->
          <!--            <a-icon slot="indicator" type="loading" />-->
          <!--          </a-spin>-->
          <a @click="addDownload(record)">下载</a>
          <!--          <span>下载中</span>-->
          <a-divider type="vertical"/>
          <a @click="collect(record)" v-if="record.isCollect === 0">收藏</a>
          <a-popconfirm
            title="取消收藏？"
            ok-text="是"
            cancel-text="否"
            v-if="record.isCollect === 1"
            @confirm="cancelCollect(record)"
          >
            <a>已收藏</a>
          </a-popconfirm>
        </template>
      </span>
    </s-table>
    <listen-music ref="listenSong" @ok="handleOk" />
  </a-card>
</template>

<script>
  // import moment from 'moment'
  import { STable } from '@/components'
  import { queryDetailByPlaylistId } from '@/api/music/song'
  import { exportSong } from '@/api/file/file'
  import ListenMusic from './modules/song/ListenSong'
  import { add, removeByUserId } from '@/api/music/collectionSong'
  import { addDownload, update } from '@/api/music/download'
  import { listAllTag } from '@/api/tag/tag'
  import { getDownloadSum } from '@/api/music/playlist'
  import { addCollectionPlaylist, removePlaylistByUserId } from '@/api/music/collectionPlaylist'

  export default {
    name: 'PlaylistDetail',
    components: {
      STable,
      ListenMusic
    },
    props: {
      fromSearchPath: {
        type: Boolean,
        default () {
          return false
        }
      },
      text: {
        type: String,
        default () {
          return ''
        }
      }
    },
    data () {
      return {
        // 高级搜索 展开/关闭
        advanced: false,
        // 查询参数
        queryParam: {},
        albums: [],
        index: -1,
        defaultImage: 'default.jpg',
        endPoint: '127.0.0.1',
        port: 9003,
        accessKey: 'root',
        secretKey: 'minio@1234',
        store: {},
        oldStore: {},
        playlist: {},
        show: {},
        preUrl: '/api/file/download/image/',
        tagText: '',
        tags: [],
        totalCount: '♪',
        downloadCount: '♪',
        // queue: {},
        // 表头
        columns: [
          {
            title: '序号',
            dataIndex: 'orderNumber',
            align: 'center',
            scopedSlots: { customRender: 'order' },
            width: 100
          },
          {
            title: '歌名',
            dataIndex: 'songName',
            align: 'center',
            scopedSlots: { customRender: 'songName' },
            sorter: true
          },
          {
            title: '歌手',
            dataIndex: 'singerName',
            align: 'center'
          },
          {
            title: '专辑',
            dataIndex: 'albumName',
            align: 'center',
            sorter: true
          },
          {
            title: '贡献者',
            dataIndex: 'contributor',
            scopedSlots: { customRender: 'contributor' },
            align: 'center'
          },
          {
            title: '下载次数',
            dataIndex: 'downloadsNumber',
            align: 'center'
          },
          {
            title: '操作',
            dataIndex: 'action',
            align: 'center',
            scopedSlots: { customRender: 'action' }
          }
        ],
        // 加载数据方法 必须为 Promise 对象
        loadData: parameter => {
          if (this.fromSearchPath) {
            this.queryParam.songName = this.text
          } else {
            this.queryParam.playlistId = this.playlist.playlistId
          }
          // 统一处理查询参数，便于后端表格DTO用固定参数接收
          const queryJson = { 'queryParam': JSON.stringify(this.queryParam) }
          return queryDetailByPlaylistId(Object.assign(parameter, queryJson))
            .then(res => {
              const count = res.data.result.totalCount
              if (this.fromSearchPath) {
                this.$emit('ok', count + ' 首单曲')
              }
              if (this.totalCount === '♪') {
                this.totalCount = count
              }
              this.lists = res.data.result.data
              return res.data.result
            })
        },
        selectedRowKeys: [],
        selectedRows: [],

        // custom table alert & rowSelection
        options: {
          alert: { show: true, clear: () => { this.selectedRowKeys = [] } },
          rowSelection: {
            selectedRowKeys: this.selectedRowKeys,
            onChange: this.onSelectChange
          }
        },
        optionAlertShow: true
      }
    },
    filters: {
      longTextFilter (text) {
        if (text.length > 8) {
          return text.substr(0, 7) + '....'
        }
        return text
      }
    },
    created () {
      this.playlist = this.$route.params
      if (this.playlist.playlistId === undefined) {
        this.playlist = JSON.parse(window.sessionStorage.getItem('playlistInfo'))
      } else {
        window.sessionStorage.setItem('playlistInfo', JSON.stringify(this.playlist))
      }
      if (this.playlist.avatar === null) {
        this.playlist.avatar = this.defaultImage
      }
      this.tableOption()
      this.getTags()
      window.addEventListener('setItem', this.listener)
      getDownloadSum({ 'playlistId': this.playlist.playlistId })
        .then(res => {
          if (res.data.message !== 'error') {
            this.downloadCount = res.data.result
          } else {
            this.$message.error('查询下载次数失败！')
          }
        })
    },
    beforeDestroy () {
      window.removeEventListener('setItem', this.listener)
    },
    methods: {
      tableOption () {
        if (!this.optionAlertShow) {
          this.options = {
            alert: { show: true, clear: () => { this.selectedRowKeys = [] } },
            rowSelection: {
              selectedRowKeys: this.selectedRowKeys,
              onChange: this.onSelectChange
            }
          }
          this.optionAlertShow = true
        } else {
          this.options = {
            alert: false,
            rowSelection: null
          }
          this.optionAlertShow = false
        }
      },
      goToSelfCenter () {
        this.$router.push({ name: 'othersCenter',
          params: this.playlist })
      },
      goSearch (text) {
        this.queryParam.playlistName = text
        this.$refs.table.refresh(false)
      },
      goUserInfo (record) {
        if (record.userId === this.$store.getters.userInfo.id) {
          this.$router.push({ name: 'selfCenter',
            params: record })
        } else {
          this.$router.push({ name: 'othersCenter',
            params: record })
        }
      },
      getTags () {
        if (this.playlist.tagId === null) {
          this.tagText = ''
          return
        }
        listAllTag()
          .then(res => {
            if (res.data.message !== 'error') {
              this.tags = res.data.result
              const chooseTags = this.playlist.tagId.split('/')
              const tagNames = []
              for (let i = 0; i < this.tags.length; i++) {
                const tag = this.tags[i].children
                for (let j = 0; j < tag.length; j++) {
                  if (chooseTags.indexOf(tag[j].tagId + '') > -1) {
                    tagNames.push(tag[j].tagName)
                  }
                }
              }
              this.tagText = tagNames.join('/')
            } else {
              this.$message.error('查询标签失败！')
            }
          })
      },
      collectPlaylist () {
        addCollectionPlaylist({ playlistId: this.playlist.playlistId })
          .then(res => {
            if (res.data.message !== 'error') {
              this.$message.success('收藏成功！')
              this.playlist.collectors++
              this.playlist.isCollect = 1
            } else {
              this.$message.error('收藏失败！')
            }
          })
      },
      cancelCollectPlaylist () {
        removePlaylistByUserId({ 'playlistId': this.playlist.playlistId })
          .then(res => {
            if (res.data.message !== 'error') {
              this.$message.success('取消收藏成功！')
              this.playlist.collectors--
              this.playlist.isCollect = 0
            } else {
              this.$message.error('取消收藏失败！')
            }
          })
      },
      listener () {
        const sessionStore = sessionStorage.getItem(String(this.$store.getters.userInfo.id))
        this.store = sessionStore === null ? {} : JSON.parse(sessionStore)
        for (const key in this.store) {
          if (this.oldStore[key] !== 100 && this.store[key] === 100) {
            update({ 'status': 1, 'downloadId': parseInt(key) })
              .then(res => {
                if (res.data.message === 'error') {
                  this.$message.error('下载失败！')
                }
              })
          }
        }
        this.oldStore = this.store
      },
      addDownload (record) {
        const shakeDownload = window.document.getElementById('shakeDownload')
        shakeDownload.classList.add('shake')
        setTimeout(() => {
          shakeDownload.classList.remove('shake')
        }, 800)
        addDownload(record)
          .then(res => {
            if (res.data.message !== 'error') {
              this.$message.success(record.songName + '开始下载')
              this.downloadCount++
              let queue = JSON.parse(sessionStorage.getItem(String(this.$store.getters.userInfo.id)))
              if (queue === null) {
                queue = {}
              }
              queue[res.data.message] = 0
              this.$addStorageEvent(2, String(this.$store.getters.userInfo.id), JSON.stringify(queue))
              record.downloadId = res.data.message
              this.download(record)
            } else {
              this.$message.error('下载失败！')
            }
          })
      },
      download (record) {
        const _that = this
        var Minio = require('minio')
        var minioClient = new Minio.Client({
          endPoint: this.endPoint,
          port: this.port,
          useSSL: false,
          accessKey: this.accessKey,
          secretKey: this.secretKey
        })
        const filepath = 'music/' + record.audioUrl
        const list = []
        let size = 0
        minioClient.getObject('music', filepath, function (err, dataStream) {
          if (err) {
            _that.downloadError(record)
            return console.log(err)
          }
          dataStream.on('data', function (chunk) {
            size += chunk.length
            list.push(chunk)
            const queue = JSON.parse(sessionStorage.getItem(String(_that.$store.getters.userInfo.id)))
            queue[record.downloadId] = Math.floor(size / record.audioSize * 100)
            _that.$addStorageEvent(2, String(_that.$store.getters.userInfo.id), JSON.stringify(queue))
          })
          dataStream.on('end', function () {
            const u8arr = new Uint8Array(size)
            let u8arrindex = 0
            for (let i = 0; i < list.length; i++) {
              for (let j = 0; j < list[i].length; j++) {
                u8arr[u8arrindex] = list[i][j]
                u8arrindex = u8arrindex + 1
              }
            }
            const blob = new Blob([u8arr])
            const reader = new FileReader()
            reader.readAsText(blob)
            reader.onload = (e) => {
              _that.downloadFile(record.songName + '.mp3', blob)
            }
          })
          dataStream.on('error', function (err) {
            _that.downloadError(record)
            console.log(err)
          })
        })
      },
      downloadError (record) {
        update({ 'status': 4, 'downloadId': parseInt(record.downloadId) })
          .then(res => {
            if (res.data.message !== 'error') {
              this.$message.error(record.songName + '下载失败')
            } else {
              this.$message.error('操作失败！')
            }
          })
      },
      reset () {
        this.queryParam = {}
        this.getPlaylistInfo()
      },
      goListen (record) {
        record.imageUrl = this.playlist.imageUrl
        this.$refs.listenSong.listenSong(record)
      },
      exportSong (record, event) {
        setTimeout(() => {
          if (event.target.style.visibility === 'hidden') {
            this.$message.warning(record.songName + '.mp3文件较大，请耐心等待，不用重复下载！')
          }
        }, 5000)
        setTimeout(() => {
          if (event.target.style.visibility === 'hidden') {
            event.target.style.visibility = 'visible'
            event.target.parentNode.childNodes[2].style.visibility = 'hidden'
            this.$message.warning(record.songName + '.mp3文件下载超时，请重试！')
          }
        }, 1800000)
        event.currentTarget.style.visibility = 'hidden'
        event.currentTarget.parentNode.childNodes[2].style.visibility = 'visible'
        exportSong({ 'fileName': record.audioUrl })
          .then(res => {
            if (res.data.message !== 'error') {
              const blob = new Blob([res.data])
              const reader = new FileReader()
              reader.readAsText(blob)
              event.target.style.visibility = 'visible'
              event.target.parentNode.childNodes[2].style.visibility = 'hidden'
              if (blob.size === 0) {
                this.$message.warning('暂无资源！')
                return
              }
              reader.onload = (e) => {
                this.downloadFile(record.songName + '.mp3', blob)
              }
            }
          })
      },
      downloadFile (title, data) {
        // for IE
        if (window.navigator && window.navigator.msSaveOrOpenBlob) {
          window.navigator.msSaveOrOpenBlob(data, title)
        } else {
          const link = document.createElement('a')
          link.href = window.URL.createObjectURL(data)
          link.download = title
          link.click()
          link.remove()
          window.URL.revokeObjectURL(link.href)
        }
      },
      handleOk () {
        this.$refs.table.clearSelected()
        this.$refs.table.refresh(false)
        this.$message.success('操作成功！')
      },
      onSelectChange (selectedRowKeys, selectedRows) {
        this.selectedRowKeys = selectedRowKeys
        this.selectedRows = selectedRows
      },
      toggleAdvanced () {
        this.advanced = !this.advanced
      },
      goToBaiDu (record, index) {
        return {
          on: {
            mouseenter: (event) => {
              record.color = true
              const background = window.document.createElement('div')
              background.className = 'background'
              background.style.width = event.currentTarget.style.width
              background.style.height = event.currentTarget.style.height
              event.currentTarget.appendChild(background)
              window.document.getElementsByTagName('body').item(0).style.cursor = 'pointer'
            },
            mouseleave: (event) => {
              record.color = false
              event.currentTarget.style.cssText = 'text-align: center'
              window.document.getElementsByTagName('body').item(0).style.cursor = 'default'
            },
            click: (event) => {
              window.open(record.musicLink)
            }
          }
        }
      },
      collect (song) {
        add({ songId: song.songId })
          .then(res => {
            if (res.data.message !== 'error') {
              this.$message.success('收藏成功！')
              this.$refs.table.refresh(true)
            } else {
              this.$message.error('收藏失败！')
            }
          })
      },
      cancelCollect (song) {
        removeByUserId({ songId: song.songId })
          .then(res => {
            if (res.data.message !== 'error') {
              this.$message.success('取消收藏成功！')
              this.$refs.table.refresh(true)
            } else {
              this.$message.error('取消收藏失败！')
            }
          })
      }
    }
  }
</script>

<style lang="less" scoped>
  .background {
    width: 100%;
    height: 100%;
    background-color: black;
    background-image: url(../../assets/backgroundColor.png) !important;
  }
  span {
    font-size: 13px;
  }
  ::v-deep .icon {
    position: absolute;
    z-index: 1;
    margin-left: 15px;
    margin-top: 5.5px;
      svg {
        width: 20px !important;
        height: 20px !important;
        color: white;
      }
  }
</style>
